package com.qiguliuxing.dts.service.seckill.mq.handler;

import com.qiguliuxing.dts.core.redis.RedisListener;
import com.qiguliuxing.dts.service.seckill.cache.SeckillCache;
import com.qiguliuxing.dts.service.seckill.constant.MessageType;
import com.qiguliuxing.dts.service.seckill.mq.message.SeckillRequestMessage;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.listener.ChannelTopic;
import org.springframework.stereotype.Service;

import javax.annotation.PostConstruct;

/**
 * Message消息的处理器
 *
 * @author 1197673878@qq.com
 * @since 2020年2月3日 下午9:21:41
 */
@Service
public class SeckillRequestHandler extends RedisListener<SeckillRequestMessage> {
    private static Log logger = LogFactory.getLog(SeckillRequestHandler.class);

    @Autowired
    private SeckillCache seckillCache;

    @PostConstruct
    public void addListener() {
        messageListenerContainer.addMessageListener(this, new ChannelTopic(MessageType.SKILL_MESSAGE));
        subscriber.addConsumer(MessageType.SKILL_MESSAGE, getClass().getSimpleName());
    }

    @Override
    protected void handler(SeckillRequestMessage message) {
        long startTime1 = System.currentTimeMillis();
        long startTime2 = System.currentTimeMillis();

        // 先看抢购是否已经结束了
        if (seckillCache.isSeckillGoodFinish(message.getSeckillGoodsId())) {
            logger.error("抱歉，您来晚了，抢购已经结束了");
            return;
        }
        long startTime3 = System.currentTimeMillis();

        // 先减缓存库存, 生成秒杀订单并存入缓存供前端获取
        if (!seckillCache.handleSeckill(message.getUserId(), message.getSeckillGoodsId(), message.getSeckillProductId(), 1, seckillCache.getSeckillGoods(message.getSeckillGoodsId()).getEndDay())) {
            // 减库存失败
            throw new RuntimeException("秒杀抢购失败，等待重试");
        }
        long startTime4 = System.currentTimeMillis();

        StringBuilder sb = new StringBuilder();
        sb.append("step1:").append(startTime2 - startTime1)
           .append("step2:").append(startTime3 - startTime2)
           .append("step3:").append(startTime4 - startTime3)
           .append("all:").append(startTime4 - startTime1);
        logger.info(sb.toString());
    }
}
